package com.ftwj.demo.base.common;

import java.lang.reflect.Field;
import java.lang.reflect.ParameterizedType;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;
import java.util.stream.Stream;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.dao.EmptyResultDataAccessException;
import org.springframework.jdbc.core.BeanPropertyRowMapper;
import org.springframework.jdbc.core.PreparedStatementCreator;
import org.springframework.jdbc.core.RowMapper;
import org.springframework.jdbc.support.GeneratedKeyHolder;
import org.springframework.jdbc.support.KeyHolder;

import com.ftwj.demo.base.annotation.Column;
import com.ftwj.demo.base.annotation.Ignore;
import com.ftwj.demo.base.annotation.Logic;
import com.ftwj.demo.base.annotation.Order;
import com.ftwj.demo.base.annotation.Primarykey;
import com.ftwj.demo.base.annotation.QueryTable;
import com.ftwj.demo.base.annotation.Table;
import com.ftwj.demo.base.annotation.Transient;
import com.ftwj.demo.base.common.inter.DaoInterface;
import com.ftwj.demo.base.constant.Const;
import com.ftwj.demo.base.constant.QueryModel;
import com.ftwj.demo.base.exception.SQLConverException;
import com.ftwj.demo.base.util.PageInfoBean;
import com.ftwj.demo.base.util.StringUtil;
import com.ftwj.demo.base.wrapper.ConditionWrapper;
import com.ftwj.demo.base.wrapper.QueryWrapper;
import com.ftwj.demo.base.wrapper.UpdateWrapper;

import cn.hutool.core.collection.CollUtil;
import cn.hutool.core.collection.CollectionUtil;
import cn.hutool.core.lang.Dict;
import cn.hutool.core.util.ArrayUtil;
import cn.hutool.core.util.ObjectUtil;
import cn.hutool.core.util.ReflectUtil;
import cn.hutool.core.util.StrUtil;
import cn.hutool.json.JSONUtil;
import cn.hutool.log.Log;
import cn.hutool.log.LogFactory;

/**
*
* <p>Title: NewBaseDao</p>  
* <p>Description: Spring JdbcTemplate Dao层基类</p>
* <p>Copyright: Copyright (c) 2020 </p>  
* <p>Company: 兰州飞天网景信息产业有限公司</p>    
* @author WangSLi
* @date 2020年2月29日 下午6:38:34
* @version V3.2
 */
public abstract class BaseDao<T,K> implements DaoInterface<T,K> {
	
	private static final Log log = LogFactory.get(BaseDao.class);
	
	@Autowired
	protected BaseJdbcTemplate jtl;
	@Autowired
	protected BaseNamedTemplate namedJtl;
	
//	@Autowired
//	protected JdbcTemplate jtl;
//	@Autowired
//	protected NamedParameterJdbcTemplate namedJtl;
	
	protected Class<T> cls;
	protected RowMapper<T> beanRowMapper;
	protected RowMapper<Map<String, Object>> mapRowMapper;
	
	@SuppressWarnings("unchecked")
	public BaseDao() {
		cls = (Class<T>)((ParameterizedType) getClass().getGenericSuperclass()).getActualTypeArguments()[0];
		beanRowMapper = new BeanPropertyRowMapper<T>(cls);
		mapRowMapper  = new RowMapper<Map<String,Object>>() {
			@Override
			public Map<String, Object> mapRow(ResultSet rs, int rowNum) throws SQLException {
				return StringUtil.rowMapper2Hump(rs);
			}
		};
	}

	public class SQLUtil {
		private String sql;
		private String totalSql;
		private Object[] values;
		public String getSql() {
			return sql;
		}
		public SQLUtil setSql(String sql) {
			this.sql = sql;
			return this;
		}
		public String getTotalSql() {
			return totalSql;
		}
		public void setTotalSql(String totalSql) {
			this.totalSql = totalSql;
		}
		public Object[] getValues() {
			return values;
		}
		public SQLUtil setValues(Object[] values) {
			this.values = values;
			return this;
		}
	}

	/*---------------------------------------------------通用新增方---------------------------------------------------*/
	
	/**
	 * 	通用插入，自增列需要添加 {@link Primarykey} 注解
	 *
	 * @param t 对象
	 * @return 操作的行数
	 */
	@Override
	public int insert(T t) {
		return insert(t, true);
	}
	
	/**
	 * 	通用插入，自增列需要添加 {@link Primarykey} 注解
	 *
	 * @param t 对象
	 * @param ignore 是否忽略 null值
	 * @return 操作的行数
	 */
	@Override
	public int insert(T t, Boolean ignore) {
		Long start = System.currentTimeMillis();
		//没有加逻辑状态则添加默认逻辑状态
		Field logicField=getLogicField();
		if(null!=logicField && null==ReflectUtil.getFieldValue(t, logicField)) {
			ReflectUtil.setFieldValue(t, logicField, getLogicNormalValue(logicField));
		}
		String table = getTableName(t);
		List<Field> filterField = getField(t, ignore);
		List<String> columnList = getColumns(filterField);
		String columns = StrUtil.join(Const.SEPARATOR_COMMA, columnList);
		String params = StrUtil.repeatAndJoin(Const.CONDITION_QUESTION, columnList.size(), Const.SEPARATOR_COMMA);
		Object[] values = filterField.stream().map(field -> ReflectUtil.getFieldValue(t, field)).toArray();
		String sql = StrUtil.format("INSERT INTO {table} ({columns}) VALUES ({params})", Dict.create().set("table", table).set("columns", columns).set("params", params));
		log.debug("\n【执行SQL】SQL：{}", sql);
		log.debug("【执行SQL】参数：{}", JSONUtil.toJsonStr(values));
		Long end = System.currentTimeMillis();
		log.debug("【SQL拼接用时】：{} 毫秒\n", (end-start));
		return jtl.update(sql, values);
	}
	
	/**
	 * 	通用插入，自增列需要添加 {@link Primarykey} 注解
	 *	新增一条记录，并且返回数据的主键
	 * @param t 对象
	 * @return 操作的行数
	 */
	@Override
	public int insertAndGetId(T t) {
		return insertAndGetId(t, true);
	}
	
	/**
	 * 	通用插入，自增列需要添加 {@link Primarykey} 注解
	 *	新增一条记录，并且返回数据的主键
	 * @param t 对象
	 * @param ignore 是否忽略 null值
	 * @return 操作的行数
	 */
	@Override
	public int insertAndGetId(T t, Boolean ignore) {
		Long start = System.currentTimeMillis();
		//没有加逻辑状态则添加默认逻辑状态
		Field logicField=getLogicField();
		if(null!=logicField && null==ReflectUtil.getFieldValue(t, logicField)) {
			ReflectUtil.setFieldValue(t, logicField, getLogicNormalValue(logicField));
		}
		String table = getTableName(t);
		List<Field> filterField = getField(t, ignore);
		List<String> columnList = getColumns(filterField);
		String columns = StrUtil.join(Const.SEPARATOR_COMMA, columnList);
		String params = StrUtil.repeatAndJoin(Const.CONDITION_QUESTION, columnList.size(), Const.SEPARATOR_COMMA);
		Object[] values = filterField.stream().map(field -> ReflectUtil.getFieldValue(t, field)).toArray();
		String sql = StrUtil.format("INSERT INTO {table} ({columns}) VALUES ({params})", Dict.create().set("table", table).set("columns", columns).set("params", params));
		//SqlParameterSource ps = new BeanPropertySqlParameterSource(t);
		 PreparedStatementCreator preparedStatementCreator = con -> {
	            PreparedStatement ps = con.prepareStatement(sql, Statement.RETURN_GENERATED_KEYS);
	            for(int i=0;i<values.length;i++){ps.setObject(i+1, values[i]);}
	            return ps;
	    };
		KeyHolder keyholder = new GeneratedKeyHolder();
		log.debug("\n【执行SQL】SQL：{}", sql);
		log.debug("【执行SQL】参数：{}", JSONUtil.toJsonStr(values));
		Long end = System.currentTimeMillis();
		log.debug("【SQL拼接用时】：{} 毫秒\n", (end-start));
		jtl.update(preparedStatementCreator, keyholder);
		return keyholder.getKey().intValue();
	}
	
	/*----------------------物理删除------------------------*/
	
	/**
	 * 	通用根据主键物理删除
	 *
	 * @param primarykey 主键
	 * @return 影响行数
	 */
	@Override
	public int delete(K primarykey) {
		Long start = System.currentTimeMillis();
		String tableName = getTableName();
		List<Field> primaryKeyList = getKeyField();
		String primaryKeycolumn = getPrimarykeyColumn(primaryKeyList);
		String sql = StrUtil.format("DELETE FROM {table} WHERE {id} = ?", Dict.create().set("table", tableName).set("id", primaryKeycolumn));
		log.debug("\n【执行SQL】SQL：{}", sql);
		log.debug("【执行SQL】参数：{}", JSONUtil.toJsonStr(primarykey));
		Long end = System.currentTimeMillis();
		log.debug("【SQL拼接用时】：{} 毫秒\n", (end-start));
		return jtl.update(sql, primarykey);
	}
	
	/**
	 * 	通用根据主键物理批量删除
	 *
	 * @param keys 主键列表
	 * @return 影响行数
	 */
	@Override
	public int delete(Object... keys) {
		Long start = System.currentTimeMillis();
		String tableName = getTableName();
		List<Field> primaryKeyList = getKeyField();
		String primaryKeycolumn = getPrimarykeyColumn(primaryKeyList);
		String params = StrUtil.repeatAndJoin(Const.CONDITION_QUESTION, keys.length, Const.SEPARATOR_COMMA);
		String sql = StrUtil.format("DELETE FROM {table} WHERE {id} IN ({keys})", Dict.create().set("table", tableName).set("id", primaryKeycolumn).set("keys", params));
		log.debug("\n【执行SQL】SQL：{}", sql);
		log.debug("【执行SQL】参数：{}", JSONUtil.toJsonStr(keys));
		Long end = System.currentTimeMillis();
		log.debug("【SQL拼接用时】：{} 毫秒\n", (end-start));
		return jtl.update(sql, keys);
	}
	
	/**
	 * 	通用根据主键物理批量删除
	 *
	 * @param keys 主键列表
	 * @return 影响行数
	 */
	@Override
	public int delete(List<K> keys) {
		return delete(keys.toArray()); 
		
	}
	
	/**
	 * 	通用根据对象物理删除
	 *
	 * @param t 删除条件
	 * @return 影响行数
	 */
	@Override
	public int deleteByExample(T t) {
		Long start = System.currentTimeMillis();
		String tableName = getTableName(t);
		List<Field> filterField = getField(t, true);
		List<String> columnList = getColumns(filterField);
		List<String> columns = columnList.stream().map(str -> StrUtil.appendIfMissing(str, Const.CONDITION_EQUALS)).collect(Collectors.toList());
		String base = StrUtil.join(Const.CONNECTOR_AND,columns.toArray());
		String params= StrUtil.format(base, columnList.toArray());
		Object[] values = filterField.stream().map(field -> ReflectUtil.getFieldValue(t, field)).toArray();
		String sql = StrUtil.format("DELETE FROM {table} WHERE {params}", Dict.create().set("table", tableName).set("params", params));
		log.debug("\n【执行SQL】SQL：{}", sql);
		log.debug("【执行SQL】参数：{}", JSONUtil.toJsonStr(values));
		Long end = System.currentTimeMillis();
		log.debug("【SQL拼接用时】：{} 毫秒\n", (end-start));
		return jtl.update(sql,values);
	}
	
	/**
	 * 	通用根据特殊条件物理删除{@link ConditionWrapper}
	 *
	 * @param t 删除条件
	 * @return 影响行数
	 */
	@Override
	public int deleteByConditions(ConditionWrapper wrapper) {
		Long start = System.currentTimeMillis();
		String tableName = getTableName();
		String params=wrapper.getBuilder().toString();
		List<Object> values = wrapper.getParameter();
		String sql = StrUtil.format("DELETE FROM {table} WHERE {params}", Dict.create().set("table", tableName).set("params", params));
		log.debug("\n【执行SQL】SQL：{}", sql);
		log.debug("【执行SQL】参数：{}", JSONUtil.toJsonStr(values));
		Long end = System.currentTimeMillis();
		log.debug("【SQL拼接用时】：{} 毫秒\n", (end-start));
		return jtl.update(sql,values.toArray());
	}
	
	/*---------------------------------------------------通用逻辑删除方法---------------------------------------------------*/

	/**
	 * 	通用根据主键逻辑删除，列需要添加 {@link Logic} 注解
	 *
	 * @param primarykey 主键
	 * @return 影响行数
	 */
	@Override
	public int remove(K primarykey) {
		Long start = System.currentTimeMillis();
		String tableName = getTableName();
		List<Field> primaryKeyList = getKeyField();
		String primaryKeycolumn = getPrimarykeyColumn(primaryKeyList);
		//获取逻辑状态字段
		Field logicField = getLogicField();
		if(null==logicField) {
			log.info("【参数异常】原因：未发现标记为逻辑状态的字段");
			throw new SQLConverException("逻辑状态字段不存在");
		}
		String column = getColumn(logicField);
		String deleteValue = getLogicDeleteValue(logicField);
		String logic=StrUtil.join(Const.SEPARATOR_EQUALS, column,deleteValue);
		String sql = StrUtil.format("UPDATE {table} SET {logic} WHERE {id} = ?", Dict.create().set("table", tableName).set("logic", logic).set("id", primaryKeycolumn));
		log.debug("\n【执行SQL】SQL：{}", sql);
		log.debug("【执行SQL】参数：{}", JSONUtil.toJsonStr(primarykey));
		Long end = System.currentTimeMillis();
		log.debug("【SQL拼接用时】：{} 毫秒\n", (end-start));
		return jtl.update(sql, primarykey);
	}
	
	/**
	 * 	通用根据主键逻辑删除，列需要添加 {@link Logic} 注解
	 *
	 * @param keys 主键列表
	 * @return 影响行数
	 */
	@Override
	public int remove(Object... keys) {
		Long start = System.currentTimeMillis();
		String tableName = getTableName();
		List<Field> primaryKeyList = getKeyField();
		String primaryKeycolumn = getPrimarykeyColumn(primaryKeyList);
		String params = StrUtil.repeatAndJoin(Const.CONDITION_QUESTION, keys.length, Const.SEPARATOR_COMMA);
		Field logicField = getLogicField();
		if(null==logicField) {
			log.info("【参数异常】原因：未发现标记为逻辑状态的字段");
			throw new SQLConverException("逻辑状态字段不存在");
		}
		String column = getColumn(logicField);
		String deleteValue = getLogicDeleteValue(logicField);
		String logic=StrUtil.join(Const.SEPARATOR_EQUALS, column,deleteValue);
		String sql = StrUtil.format("UPDATE {table} SET {logic} WHERE {id} IN ({keys})", Dict.create().set("table", tableName).set("logic", logic).set("id", primaryKeycolumn).set("keys", params));
		log.debug("\n【执行SQL】SQL：{}", sql);
		log.debug("【执行SQL】参数：{}", JSONUtil.toJsonStr(keys));
		Long end = System.currentTimeMillis();
		log.debug("【SQL拼接用时】：{} 毫秒\n", (end-start));
		return jtl.update(sql, keys);
	}
	
	/**
	 * 	通用根据主键逻辑删除，列需要添加 {@link Logic} 注解
	 *
	 * @param keys 主键列表
	 * @return 影响行数
	 */
	@Override
	public int remove(List<K> keys) {
		return remove(keys.toArray());
	}
	
	/**
	 * 	通用根据对象逻辑删除
	 *
	 * @param t 删除条件
	 * @return 影响行数
	 */
	@Override
	public int removeByExample(T t) {
		Long start = System.currentTimeMillis();
		String tableName = getTableName(t);
		Field logicField = getLogicField();
		if(null==logicField) {
			log.info("【参数异常】原因：未发现标记为逻辑状态的字段");
			throw new SQLConverException("逻辑状态字段不存在");
		}
		String logicColumn = getColumn(logicField);
		String deleteValue = getLogicDeleteValue(logicField);
		String logic=StrUtil.join(Const.SEPARATOR_EQUALS, logicColumn,deleteValue);
		List<Field> filterField = getField(t, true);
		List<String> columnList = getColumns(filterField);
		List<String> columns = columnList.stream().map(str -> StrUtil.appendIfMissing(str, Const.CONDITION_EQUALS)).collect(Collectors.toList());
		String base = StrUtil.join(Const.CONNECTOR_AND,columns.toArray());
		String params= StrUtil.format(base, columnList.toArray());
		Object[] values = filterField.stream().map(field -> ReflectUtil.getFieldValue(t, field)).toArray();
		String sql = StrUtil.format("UPDATE {table} SET {logic} WHERE {params}", Dict.create().set("table", tableName).set("logic", logic).set("params", params));
		log.debug("\n【执行SQL】SQL：{}", sql);
		log.debug("【执行SQL】参数：{}", JSONUtil.toJsonStr(values));
		Long end = System.currentTimeMillis();
		log.debug("【SQL拼接用时】：{} 毫秒\n", (end-start));
		return jtl.update(sql,values);
	}
	
	/**
	 * 	通用特殊条件逻辑删除
	 *
	 * @param wrapper 条件构造器
	 * @return 影响行数
	 */
	@Override
	public int removeByConditions(ConditionWrapper wrapper) {
		Long start = System.currentTimeMillis();
		String tableName = getTableName();
		Field logicField = getLogicField();
		if(null==logicField) {
			log.info("【参数异常】原因：未发现标记为逻辑状态的字段");
			throw new SQLConverException("逻辑状态字段不存在");
		}
		String logicColumn = getColumn(logicField);
		String deleteValue = getLogicDeleteValue(logicField);
		String logic=StrUtil.join(Const.SEPARATOR_EQUALS, logicColumn,deleteValue);
		String params=wrapper.getBuilder().toString();
		List<Object> values = wrapper.getParameter();
		String sql = StrUtil.format("UPDATE {table} SET {logic} WHERE {params}", Dict.create().set("table", tableName).set("logic", logic).set("params", params));
		log.debug("\n【执行SQL】SQL：{}", sql);
		log.debug("【执行SQL】参数：{}", JSONUtil.toJsonStr(values));
		Long end = System.currentTimeMillis();
		log.debug("【SQL拼接用时】：{} 毫秒\n", (end-start));
		return jtl.update(sql,values.toArray());
	}
	
	/*---------------------------------------------------通用修改方法---------------------------------------------------*/
	
	/**
	 * 	通用根据主键更新，自增列需要添加 {@link Primarykey} 注解
	 *
	 * @param t  对象
	 * @return 操作的行数
	 */
	@Override
	public int update(T t) {
		return update(t, true);
	}
	
	/**
	 * 	通用根据主键更新，自增列需要添加 {@link Primarykey} 注解
	 *
	 * @param t  对象
	 * @param ignore 是否忽略 null 值
	 * @return 操作的行数
	 */
	@Override
	public int update(T t, Boolean ignore) {
		Long start = System.currentTimeMillis();
		String tableName = getTableName(t);
		List<Field> filterField = getField(t, ignore);
		List<String> columnList = getColumns(filterField);
		List<String> columns = columnList.stream().map(str -> StrUtil.appendIfMissing(str, Const.CONDITION_EQUALS)).collect(Collectors.toList());
		String params = StrUtil.join(Const.SEPARATOR_COMMA, columns);
		List<Field> primaryKeyList = getKeyField();
		List<String> primaryKeycolumnList = getPrimarykeyColumns(primaryKeyList);
		List<String> primaryKeys = primaryKeycolumnList.stream().map(field -> StrUtil.appendIfMissing(field, Const.CONDITION_EQUALS)).collect(Collectors.toList());		
		String paramKeys = StrUtil.join(Const.CONNECTOR_AND, primaryKeys);		
		List<Object> valueList = filterField.stream().map(field -> ReflectUtil.getFieldValue(t, field)).collect(Collectors.toList());
		List<Object> primarykeysValue = primaryKeyList.stream().map(action -> ReflectUtil.getFieldValue(t, action)).collect(Collectors.toList());
		valueList.addAll(primarykeysValue);
		Object[] values = ArrayUtil.toArray(valueList, Object.class);
		String sql = StrUtil.format("UPDATE {table} SET {params} WHERE {id}", Dict.create().set("table", tableName).set("params", params).set("id", paramKeys));
		log.debug("\n【执行SQL】SQL：{}", sql);
		log.debug("【执行SQL】参数：{}", JSONUtil.toJsonStr(values));
		Long end = System.currentTimeMillis();
		log.debug("【SQL拼接用时】：{} 毫秒\n", (end-start));
		return jtl.update(sql, values);
	}
	
	/**
	 * 	通用根据字段更新，自增列需要添加 {@link Primarykey} 注解
	 *
	 * @param t  对象
	 * @param fieldList 更新条件(T中的作为条件的字段名列表)并忽略其中的 null值
	 * @return 操作的行数
	 */
	@Override
	public int updateByExample(T t, String... fieldArrays) {
		List<String> fieldList=CollectionUtil.toList(fieldArrays);
		return updateByExample(t, fieldList, true); 
	}
	
	/**
	 * 	通用根据字段更新，自增列需要添加 {@link Primarykey} 注解
	 *
	 * @param t  对象
	 * @param fieldList 更新条件(T中的作为条件的字段名列表)
	 * @param ignore 是否忽略 null 值
	 * @return 操作的行数
	 */
	@Override
	public int updateByExample(T t, Boolean ignore, String... fieldArrays) {
		List<String> fieldList=CollectionUtil.toList(fieldArrays);
		return updateByExample(t, fieldList, ignore); 
	}
	
	/**
	 * 	通用根据主键更新，自增列需要添加 {@link Primarykey} 注解
	 *
	 * @param t  对象
	 * @param fieldList 更新条件(T中的作为条件的字段名列表)并忽略其中的 null值
	 * @return 操作的行数
	 */
	@Override
	public int updateByExample(T t, List<String> fieldList) {
		return updateByExample(t, fieldList, true); 
	}
	
	/**
	 * 	通用根据字段更新，自增列需要添加 {@link Primarykey} 注解
	 *
	 * @param t  对象
	 * @param fieldList 更新条件(T中的作为条件的字段名列表)
	 * @param ignore 是否忽略 null 值
	 * @return 操作的行数
	 */
	@Override
	public int updateByExample(T t, List<String> fieldList, Boolean ignore) {
		Long start = System.currentTimeMillis();
		String tableName = getTableName(t);
		List<Field> filterField = getField(t, ignore);
		List<String> columnList = getColumns(filterField);
		List<Field> fields = fieldList.stream().map(condition -> ReflectUtil.getField(t.getClass(), condition)).collect(Collectors.toList());
		List<Object> paramList = fields.stream().map(field -> ReflectUtil.getFieldValue(t, field)).collect(Collectors.toList());
		List<String> conditionColumnList = getColumns(fields);
		List<String> columns = columnList.stream().filter(column -> !CollectionUtil.contains(conditionColumnList, column)).map(s -> StrUtil.appendIfMissing(s, Const.CONDITION_EQUALS)).collect(Collectors.toList());
		String params = StrUtil.join(Const.SEPARATOR_COMMA, columns);
		List<Object> valueList = filterField.stream().filter(field -> !CollectionUtil.contains(fields, field)).map(field -> ReflectUtil.getFieldValue(t, field)).collect(Collectors.toList());
		List<String> conditionColumns = conditionColumnList.stream().map(field -> StrUtil.appendIfMissing(field, Const.CONDITION_EQUALS)).collect(Collectors.toList());		
		String conditions = StrUtil.join(Const.CONNECTOR_AND, conditionColumns);
		valueList.addAll(paramList);
		Object[] values = ArrayUtil.toArray(valueList, Object.class);
		String sql = StrUtil.format("UPDATE {table} SET {params} WHERE {conditions}", Dict.create().set("table", tableName).set("params", params).set("conditions", conditions));
		log.debug("\n【执行SQL】SQL：{}", sql);
		log.debug("【执行SQL】参数：{}", JSONUtil.toJsonStr(values));
		Long end = System.currentTimeMillis();
		log.debug("【SQL拼接用时】：{} 毫秒\n", (end-start));
		return jtl.update(sql, values);
	}

	/**
	 * 	通用特殊条件修改
	 *
	 * @param wrapper 修改条件构造器
	 * @return 影响行数
	 */
	@Override
	public int updateByConditions(UpdateWrapper wrapper) {
		Long start = System.currentTimeMillis();
		String tableName = getTableName();
		String set=wrapper.getUpdate().toString();
		String params=wrapper.getBuilder().toString();
		List<Object> values = wrapper.getParameter();
		String sql = StrUtil.format("UPDATE {table} SET {set} WHERE {params}", Dict.create().set("table", tableName).set("set", set).set("params", params));
		log.debug("\n【执行SQL】SQL：{}", sql);
		log.debug("【执行SQL】参数：{}", JSONUtil.toJsonStr(values));
		Long end = System.currentTimeMillis();
		log.debug("【SQL拼接用时】：{} 毫秒\n", (end-start));
		return jtl.update(sql, values.toArray());
	}

	/*---------------------------------------------------通用条件查询---------------------------------------------------*/
	
	/**
	 * 	通用根据主键查询单条记录
	 *
	 * @param primarykey 主键
	 * @return 单条记录BEAN
	 */
	@Override
	public T query(K primarykey) {
		SQLUtil util = buildQuery(primarykey);
		try {
			T res = jtl.queryForObject(util.getSql(), util.getValues(), beanRowMapper);
			return res;
		} catch (EmptyResultDataAccessException e) {
			log.info("\n【执行SQL】：查询结果为空！\n");
			return null;
		}
	}

	/**
	 * 	通用根据主键查询单条记录
	 *
	 * @param primarykey 主键
	 * @return 单条记录MAP
	 */
	@Override
	public Map<String,Object> queryMap(K primarykey) {
		SQLUtil util = buildQuery(primarykey);
		try {
			return jtl.queryForObject(util.getSql(), util.getValues(), mapRowMapper);
		} catch (EmptyResultDataAccessException e) {
			log.info("\n【执行SQL】：查询结果为空！\n");
			return null;
		}
	}
	/**
	 * 	不根据任何条件查询记录
	 *
	 * @return 记录列表
	 */
	@Override
	public List<Map<String, Object>> queryList() {
		Long start = System.currentTimeMillis();
		String tableName = getTableName();
		List<Field> columnsField = getIgnoreField(false);
		List<String> columnsList = getColumns(columnsField);
		String queryColumns = StrUtil.join(Const.SEPARATOR_COMMA, columnsList);
		String sql = StrUtil.format("SELECT {columns} FROM {table} ",Dict.create().set("columns", queryColumns).set("table", tableName));
		log.debug("\n【执行SQL】SQL：{}", sql);
		Long end = System.currentTimeMillis();
		log.debug("【SQL拼接用时】：{} 毫秒\n", (end-start));
		return jtl.queryForList(sql);
	}

	/**
	 * 	通用根据主键数组查询记录
	 *
	 * @param primarykey 主键
	 * @return 单条记录
	 */
	@Override
	public List<T> queryListByIds(Object... primarykey) {
		SQLUtil util=buildQueryListByIds(primarykey);
		return jtl.query(util.getSql(), util.getValues(), beanRowMapper);
	}
	
	/**
	 * 	通用根据主键数组查询记录
	 *
	 * @param primarykey 主键
	 * @return 单条记录
	 */
	@Override
	public List<Map<String,Object>> queryListMapByIds(Object... primarykey) {
		SQLUtil util=buildQueryListByIds(primarykey);
		return jtl.query(util.getSql(), util.getValues(), mapRowMapper);
	}
	
	/**
	 * 	通用根据主键查询单条记录 （联合主键，未测试）
	 *
	 * @param primarykey 主键
	 * @return 单条记录
	 */
	@Override
	public T queryByUniteId(Object... primarykey) {
		SQLUtil util=buildQueryByUniteId(primarykey);
		try {
			return jtl.queryForObject(util.getSql(), util.getValues(), beanRowMapper);
		} catch (EmptyResultDataAccessException e) {
			log.info("\n【执行SQL】：查询结果为空！\n");
			return null;
		}
	}
	
	/**
	 * 	通用根据主键查询单条记录 （联合主键，未测试）
	 *
	 * @param primarykey 主键
	 * @return 单条记录
	 */
	@Override
	public Map<String, Object> queryMapByUniteId(Object... primarykey) {
		SQLUtil util=buildQueryByUniteId(primarykey);
		try {
			return jtl.queryForObject(util.getSql(), util.getValues(), mapRowMapper);
		} catch (EmptyResultDataAccessException e) {
			log.info("\n【执行SQL】：查询结果为空！\n");
			return null;
		}
	}
	
	/**
	 * 	根据对象和条件构造查询
	 *
	 * @param t 查询条件
	 * @param wapper 条件构造器
	 * @return 对象列表
	 */
	@Override
	public List<T> queryListByConditions(T t,QueryWrapper wrapper) {
		SQLUtil util=buildQueryListByConditions(t, wrapper);
		return jtl.query(util.getSql(), util.getValues(),beanRowMapper);
	}
	
	/**
	 * 	根据对象和条件构造查询
	 *
	 * @param t 查询条件
	 * @param wapper 条件构造器
	 * @return 对象列表
	 */
	@Override
	public List<Map<String, Object>> queryListMapByConditions(T t, QueryWrapper wrapper) {
		SQLUtil util=buildQueryListByConditions(t, wrapper);
		return jtl.query(util.getSql(), util.getValues(),mapRowMapper);
	}
	
	/**
	 * 	根据对象查询单条数据，若查询结果为多个则取第一条
	 *
	 * @param t 查询条件
	 * @return 对象
	 */
	@Override
	public T queryByExample(T t) {
		SQLUtil util=bulidQueryByExample(t);
		try {
			return jtl.queryForObject(util.getSql(), util.getValues(), beanRowMapper);
		} catch (EmptyResultDataAccessException e) {
			log.info("\n【执行SQL】：查询结果为空！\n");
			return null;
		}
	}
	
	/**
	 * 	根据对象查询
	 *
	 * @param t 查询条件，若查询结果为多个则取第一条
	 * @return Map
	 */
	@Override
	public Map<String, Object> queryMapByExample(T t) {
		SQLUtil util=bulidQueryByExample(t);
		try {
			return jtl.queryForObject(util.getSql(), util.getValues(), mapRowMapper);
		} catch (EmptyResultDataAccessException e) {
			log.info("\n【执行SQL】：查询结果为空！\n");
			return null;
		}
	}
	
	/**
	 * 	根据对象查询
	 *
	 * @param t 查询条件
	 * @return 对象列表
	 */
	@Override
	public List<T> queryListByExample(T t) {
		SQLUtil util=bulidQueryListByExample(t);
		return jtl.query(util.getSql(), util.getValues(), beanRowMapper);
	}
	
	/**
	 * 	根据对象查询
	 *
	 * @param t 查询条件
	 * @return Map列表
	 */
	@Override
	public List<Map<String, Object>> queryListMapByExample(T t) {
		SQLUtil util=bulidQueryListByExample(t);
		return jtl.query(util.getSql(), util.getValues(), mapRowMapper);
		
	}
	
	/**
	 * 	根据条件构造查询
	 *
	 * @param wapper 条件构造器
	 * @return 对象
	 */
	@Override
	public T queryByConditions(QueryWrapper wrapper) {
		SQLUtil util=buildQueryListByConditions(wrapper);
		try {
			return jtl.queryForObject(util.getSql(), util.getValues(),beanRowMapper);
		} catch (EmptyResultDataAccessException e) {
			log.info("\n【执行SQL】：查询结果为空！\n");
			return null;
		}
	}
	
	/**
	 * 	根据条件构造查询
	 *
	 * @param wapper 条件构造器
	 * @return Map
	 */
	@Override
	public Map<String, Object> queryMapByConditions(QueryWrapper wrapper) {
		SQLUtil util=buildQueryListByConditions(wrapper);
		try {
			return jtl.queryForObject(util.getSql(), util.getValues(),mapRowMapper);
		} catch (EmptyResultDataAccessException e) {
			log.info("\n【执行SQL】：查询结果为空！\n");
			return null;
		}
	}
	
	/**
	 * 	根据条件构造查询
	 *
	 * @param wapper 条件构造器
	 * @return 对象列表
	 */
	@Override
	public List<T> queryListByConditions(QueryWrapper wrapper) {
		SQLUtil util=buildQueryListByConditions(wrapper);
		return jtl.query(util.getSql(), util.getValues(),beanRowMapper);
	}
	
	/**
	 * 	根据条件构造查询
	 *
	 * @param wapper 条件构造器
	 * @return Map列表
	 */
	@Override
	public List<Map<String, Object>> queryListMapByConditions(QueryWrapper wrapper) {
		SQLUtil util=buildQueryListByConditions(wrapper);
		return jtl.query(util.getSql(), util.getValues(),mapRowMapper);
	}
	
	/**
	 * 	根据条件构造查询
	 *
	 * @param wapper 条件构造器
	 * @return 总条数
	 */
	@Override
	public Integer queryCount(QueryWrapper wrapper) {
		Long start = System.currentTimeMillis();
		String tableName = getTableName();
		Field logicField=getLogicField();
		String logic=buildLogic(logicField);
		List<Object> values = wrapper.getParameter();
		String totalSql = StrUtil.format("SELECT IFNULL(COUNT(1),0) FROM {table} WHERE {logic} AND {wapper}", 
				Dict.create().set("table", tableName)
							 .set("logic", logic)
							 .set("wapper", wrapper.getBuilder().toString()));
		log.debug("\n【执行SQL】SQL：{}", totalSql);
		log.debug("【执行SQL】参数：{}\n", JSONUtil.toJsonStr(values));
		Long end = System.currentTimeMillis();
		log.debug("【SQL拼接用时】：{} 毫秒\n", (end-start));
		return jtl.queryForObject(totalSql, values.toArray(),Integer.class);
	}
	
	/*---------------------------------------------------通用分页查询方法---------------------------------------------------*/
	
	/**
	 * 	根据对象分页查询（默认当前页：1，每页条数：10）
	 *
	 * @return 分页对象PageInfoBean<Bean>
	 */
	@Override
	public PageInfoBean page(int curPage,int perPage) {
		PageInfoBean page=new PageInfoBean();
		page.setCurPage(curPage);
		page.setPerPage(perPage);
		return pageByExample(ReflectUtil.newInstance(cls),page);
	}
	
	/**
	 * 	根据对象分页查询（默认当前页：1，每页条数：10）
	 *
	 * @return 分页对象PageInfoBean<Map>
	 */
	@Override
	public PageInfoBean pageMap(int curPage,int perPage) {
		PageInfoBean page=new PageInfoBean();
		page.setCurPage(curPage);
		page.setPerPage(perPage);
		return pageMapByExample(ReflectUtil.newInstance(cls),page);
	}
	
	/**
	 * 	根据对象和条件分页查询（默认当前页：1，每页条数：10）
	 *
	 * @param wapper 条件构造器
	 * @return 分页对象PageInfoBean<Bean>
	 */
	@Override
	public PageInfoBean pageByConditions(QueryWrapper wrapper,PageInfoBean page) {
		SQLUtil util=buildPageByConditions(wrapper, page);
		int total=jtl.queryForObject(util.getTotalSql(), util.getValues(),Integer.class);
		//计算出page的参数值
		page.setTotalNum(total);
		page.calPageParam();
		List<T> list = jtl.query(StrUtil.format(util.getSql(),Dict.create().set("start", page.getStartIndex())), util.getValues(), beanRowMapper);
		page.setRecList(list);
		return page;
	}
	
	/**
	 * 	根据对象和条件分页查询（默认当前页：1，每页条数：10）
	 *
	 * @param wapper 条件构造器
	 * @return 分页对象PageInfoBean<Bean>
	 */
	@Override
	public PageInfoBean pageMapByConditions(QueryWrapper wrapper,PageInfoBean page) {
		SQLUtil util=buildPageByConditions(wrapper, page);
		int total=jtl.queryForObject(util.getTotalSql(), util.getValues(),Integer.class);
		//计算出page的参数值
		page.setTotalNum(total);
		page.calPageParam();
		List<Map<String, Object>> list = jtl.query(StrUtil.format(util.getSql(),Dict.create().set("start", page.getStartIndex())), util.getValues(), mapRowMapper);
		page.setRecList(list);
		return page;
	}
	
	/**
	 * 	根据对象和条件分页查询（默认当前页：1，每页条数：10）
	 *
	 * @param t 查询条件
	 * @param wapper 条件构造器
	 * @return 分页对象PageInfoBean<Bean>
	 */
	@Override
	public PageInfoBean pageByConditions(T t, QueryWrapper wrapper, PageInfoBean page) {
		SQLUtil util=buildPageByConditions(t, wrapper, page);
		int total=jtl.queryForObject(util.getTotalSql(), util.getValues(),Integer.class);
		//计算出page的参数值
		page.setTotalNum(total);
		page.calPageParam();
		List<T> list = jtl.query(StrUtil.format(util.getSql(),Dict.create().set("start", page.getStartIndex())), util.getValues(), beanRowMapper);
		page.setRecList(list);
		return page;
	}
	
	/**
	 * 	根据对象和条件分页查询（默认当前页：1，每页条数：10）
	 *
	 * @param t 查询条件
	 * @param wapper 条件构造器
	 * @return 分页对象PageInfoBean<Bean>
	 */
	@Override
	public PageInfoBean pageMapByConditions(T t, QueryWrapper wrapper, PageInfoBean page) {
		SQLUtil util=buildPageByConditions(t, wrapper, page);
		int total=jtl.queryForObject(util.getTotalSql(), util.getValues(),Integer.class);
		//计算出page的参数值
		page.setTotalNum(total);
		page.calPageParam();
		List<Map<String, Object>> list = jtl.query(StrUtil.format(util.getSql(),Dict.create().set("start", page.getStartIndex())), util.getValues(), mapRowMapper);
		page.setRecList(list);
		return page;
	}
	
	/**
	 * 	根据对象分页查询（默认当前页：1，每页条数：10）
	 *
	 * @param t 查询条件
	 * @return 分页对象PageInfoBean<Bean>
	 */
	@Override
	public PageInfoBean pageByExample(T t,PageInfoBean page) {
		SQLUtil util=buildPageByExample(t, page);
		int total=jtl.queryForObject(util.getTotalSql(), util.getValues(),Integer.class);
		//计算出page的参数值
		page.setTotalNum(total);
		page.calPageParam();
		List<T> list = jtl.query(StrUtil.format(util.getSql(),Dict.create().set("start", page.getStartIndex())), util.getValues(), beanRowMapper);
		page.setRecList(list);
		return page;
	}
	
	/**
	 * 	根据对象分页查询（默认当前页：1，每页条数：10）
	 *
	 * @param t 查询条件
	 * @return 分页对象PageInfoBean<Map>
	 */
	@Override
	public PageInfoBean pageMapByExample(T t,PageInfoBean page) {
		SQLUtil util=buildPageByExample(t, page);
		int total=jtl.queryForObject(util.getTotalSql(), util.getValues(),Integer.class);
		//计算出page的参数值
		page.setTotalNum(total);
		page.calPageParam();
		Integer start=page.getStartIndex();
		List<Map<String, Object>> list = jtl.query(StrUtil.format(util.getSql(),Dict.create().set("start", start)), util.getValues(), mapRowMapper);
		page.setRecList(list);
		return page;
	}
	
	/*---------------------------------------------------BUILD SQL方法---------------------------------------------------*/
	
	/**
	 * 
	 * <p>Title: buildLogic</p>  
	 * <p>Description: 构建SQL:逻辑未删除</p>  
	 * @return 
	 * @author WangSLi
	 * @date 2020年3月16日  
	 * @version 1.0
	 */
	private String buildLogic(Field field) {
		String logic="TRUE";
		if(null != field) {
			String column = getColumn(field);
			String normalValue = getLogicNormalValue(field);
			logic=StrUtil.join(Const.SEPARATOR_EQUALS, column,normalValue);
		}
		return logic;
	}
	
	private String buildOrder(List<Field> fieldList) {
		// 构造列
		List<String> orderList = CollectionUtil.newArrayList();
		for(Field field:fieldList) {
			Integer sort=getOrderSort(field);
			String column=getColumn(field);
			String order = getOrderWay(field);
			orderList.add(StrUtil.join(Const.SEPARATOR_SPACE,sort+"@"+column,order));
		}
		List<String> bulidList=orderList.stream().sorted().map(mapper -> mapper.indexOf("@")!=-1?mapper.split("@")[1]:"").collect(Collectors.toList());
		String bulid = Const.ORDER_BY+StrUtil.join(Const.SEPARATOR_COMMA, bulidList);
		return bulid;
	}
	
	/**
	 * 
	 * <p>Title: buildLogic</p>  
	 * <p>Description: 构建SQL:特殊条件查询</p>  
	 * @return 
	 * @author WangSLi
	 * @date 2020年3月16日  
	 * @version 1.0
	 */
	/*
	private static List<String> buildQueryTable() {
		List<Field> logicField = getQuertField();
		List<String> querys = logicField.stream().map(field -> StrUtil.join(" ",getQueryTable(field))).collect(Collectors.toList());
		return querys;
	}
	*/
	
	/**
	 * 
	 * <p>Title: whereBuild</p>  
	 * <p>Description: 构建SQL:构建查询条件语句</p>  
	 * @return 
	 * @author WangSLi
	 * @date 2020年3月18日  
	 * @version 1.0
	 */
	private String buildWhere(List<Field> fieilds) {
		List<String> querys = fieilds.stream().map(field -> StrUtil.join(" ",getColumn(field),getQueryTable(field))).collect(Collectors.toList());
		String where = StrUtil.addPrefixIfNot(StrUtil.join(Const.CONNECTOR_AND, querys.toArray()), Const.CONNECTOR_AND);
		return where;
	}

	private SQLUtil buildQuery(K primarykey) {
		Long start = System.currentTimeMillis();
		String tableName = getTableName();
		Field logicField=getLogicField();
		String logic=buildLogic(logicField);
		List<Field> filterField = getIgnoreField(true);
		List<String> columnList = getColumns(filterField);
		List<Field> primaryKeyList = getKeyField();
		List<String> primaryKeycolumnList = getPrimarykeyColumns(primaryKeyList);
		List<Field> orderFile = getOrderField();
		String order = buildOrder(orderFile);
		List<String> primaryKeys = primaryKeycolumnList.stream().map(field -> StrUtil.appendIfMissing(field, Const.CONDITION_EQUALS)).collect(Collectors.toList());		
		String columns = StrUtil.join(Const.SEPARATOR_COMMA, columnList);
		String paramKeys = StrUtil.join(Const.CONNECTOR_AND, primaryKeys);	
		String sql = StrUtil.format("SELECT {columns} FROM {table} WHERE {logic} AND {params} {order}", Dict.create().set("columns", columns).set("table", tableName).set("logic", logic).set("params", paramKeys).set("order", Const.ORDER_BY.equals(order)?"":order));
		log.debug("\n【执行SQL】SQL：{}", sql);
		log.debug("【执行SQL】参数：{}", JSONUtil.toJsonStr(primarykey));
		Long end = System.currentTimeMillis();
		log.debug("【SQL拼接用时】：{} 毫秒\n", (end-start));
		SQLUtil util=new SQLUtil();
		util.setSql(sql);
		util.setValues(new Object[] {primarykey});
		return util;
	}
	
	private SQLUtil buildQueryListByIds(Object... primarykey) {
		Long start = System.currentTimeMillis();
		String tableName = getTableName();
		Field logicField=getLogicField();
		String logic=buildLogic(logicField);
		List<Field> filterField = getIgnoreField(true);
		List<String> columnList = getColumns(filterField);
		List<Field> primaryKeyList = getKeyField();
		String primaryKeycolumn = getPrimarykeyColumn(primaryKeyList);	
		List<Field> orderFile = getOrderField();
		String order = buildOrder(orderFile);
		String columns = StrUtil.join(Const.SEPARATOR_COMMA, columnList);
		String params = StrUtil.repeatAndJoin(Const.CONDITION_QUESTION, primarykey.length, Const.SEPARATOR_COMMA);	
		String sql = StrUtil.format("SELECT {columns} FROM {table} WHERE {logic} AND {id} IN ({keys}) {order} ", Dict.create().set("columns", columns).set("table", tableName).set("logic", logic).set("id", primaryKeycolumn).set("keys", params).set("order", Const.ORDER_BY.equals(order)?"":order));
		log.debug("\n【执行SQL】SQL：{}", sql);
		log.debug("【执行SQL】参数：{}", JSONUtil.toJsonStr(primarykey));
		Long end = System.currentTimeMillis();
		log.debug("【SQL拼接用时】：{} 毫秒\n", (end-start));
		SQLUtil util=new SQLUtil();
		util.setSql(sql);
		util.setValues(primarykey);
		return util;
		
	}
	
	private SQLUtil buildQueryByUniteId(Object... primarykey) {
		Long start = System.currentTimeMillis();
		String tableName = getTableName();
		Field logicField=getLogicField();
		String logic=buildLogic(logicField);
		List<Field> filterField = getIgnoreField(true);
		List<String> columnList = getColumns(filterField);
		String columns = StrUtil.join(Const.SEPARATOR_COMMA, columnList);
		List<Field> primaryKeyList = getKeyField();
		List<String> primaryKeycolumnList = getPrimarykeyColumns(primaryKeyList);
		List<Field> orderFile = getOrderField();
		String order = buildOrder(orderFile);
		List<String> primaryKeys = primaryKeycolumnList.stream().map(field -> StrUtil.appendIfMissing(field, Const.CONDITION_EQUALS)).collect(Collectors.toList());		
		String paramKeys = StrUtil.join(Const.CONNECTOR_AND, primaryKeys);	
		String sql = StrUtil.format("SELECT {columns} FROM {table} WHERE {logic} AND {params} {order}", Dict.create().set("columns", columns).set("table", tableName).set("logic", logic).set("params", paramKeys).set("order", Const.ORDER_BY.equals(order)?"":order));
		log.debug("\n【执行SQL】SQL：{}", sql);
		log.debug("【执行SQL】参数：{}", JSONUtil.toJsonStr(primarykey));
		Long end = System.currentTimeMillis();
		log.debug("【SQL拼接用时】：{} 毫秒\n", (end-start));
		SQLUtil util=new SQLUtil();
		util.setSql(sql);
		util.setValues(primarykey);
		return util;
	}
	
	private SQLUtil buildQueryListByConditions(T t,QueryWrapper wrapper) {
		Long start = System.currentTimeMillis();
		String tableName = getTableName(t);
		Field logicField=getLogicField();
		String logic=buildLogic(logicField);
		List<Field> columnsField = getIgnoreField(true);
		String queryColumns=wrapper.getSelect().toString();
		if(StrUtil.isBlank(queryColumns)) {
			List<String> columnsList = getColumns(columnsField);
			queryColumns = StrUtil.join(Const.SEPARATOR_COMMA, columnsList);
		}
		String subquery= wrapper.getSubquery().toString();
		if(StrUtil.isNotBlank(queryColumns)&&StrUtil.isNotBlank(subquery)) {
			subquery=Const.SEPARATOR_COMMA+subquery;
		}
		List<Field> filterField = getField(t, true);
		String where = buildWhere(filterField);
		List<Object> values = filterField.stream().map(field -> ReflectUtil.getFieldValue(t, field)).collect(Collectors.toList());
		CollectionUtil.addAll(values,wrapper.getParameter());
		String sql = StrUtil.format("SELECT {columns} {subquery} FROM {table} {as} WHERE {logic} {where} AND {wapper}",
				Dict.create().set("columns", queryColumns)
							 .set("subquery", subquery)
							 .set("table", tableName)
							 .set("as", Const.CONNECTOR_AS+wrapper.getTableAs())
							 .set("logic", logic)
							 .set("where", StrUtil.isBlank(where) ? "" : where)
							 .set("wapper", wrapper.getBuilder().toString()));
		log.debug("\n【执行SQL】SQL：{}", sql);
		log.debug("【执行SQL】参数：{}", JSONUtil.toJsonStr(values));
		Long end = System.currentTimeMillis();
		log.debug("【SQL拼接用时】：{} 毫秒\n", (end-start));
		SQLUtil util=new SQLUtil();
		util.setSql(sql);
		util.setValues(values.toArray());
		return util;
	}
	
	private SQLUtil bulidQueryListByExample(T t) {
		Long start = System.currentTimeMillis();
		String tableName = getTableName(t);
		Field logicField=getLogicField();
		String logic=buildLogic(logicField);
		List<Field> columnsField = getIgnoreField(true);
		List<String> columnsList = getColumns(columnsField);
		String queryColumns = StrUtil.join(Const.SEPARATOR_COMMA, columnsList);
		List<Field> filterField = getField(t, true);
		List<Field> orderFile = getOrderField();
		String order = buildOrder(orderFile);
		String where = buildWhere(filterField);
		Object[] values = filterField.stream().map(field -> ReflectUtil.getFieldValue(t, field)).toArray();
		String sql = StrUtil.format("SELECT {columns} FROM {table} WHERE {logic} {where} {order}"
				, Dict.create().set("columns", queryColumns).set("table", tableName).set("logic", logic).set("where", StrUtil.isBlank(where) ? "" : where).set("order", Const.ORDER_BY.equals(order)?"":order));
		log.debug("\n【执行SQL】SQL：{}", sql);
		log.debug("【执行SQL】参数：{}", JSONUtil.toJsonStr(values));
		Long end = System.currentTimeMillis();
		log.debug("【SQL拼接用时】：{} 毫秒\n", (end-start));
		SQLUtil util=new SQLUtil();
		util.setSql(sql);
		util.setValues(values);
		return util;
	}
	
	private SQLUtil bulidQueryByExample(T t) {
		Long start = System.currentTimeMillis();
		String tableName = getTableName(t);
		Field logicField=getLogicField();
		String logic=buildLogic(logicField);
		List<Field> columnsField = getIgnoreField(true);
		List<String> columnsList = getColumns(columnsField);
		String queryColumns = StrUtil.join(Const.SEPARATOR_COMMA, columnsList);
		List<Field> filterField = getField(t, true);
		List<Field> orderFile = getOrderField();
		String order = buildOrder(orderFile);
		String where = buildWhere(filterField);
		Object[] values = filterField.stream().map(field -> ReflectUtil.getFieldValue(t, field)).toArray();
		String sql = StrUtil.format("SELECT {columns} FROM {table} WHERE {logic} {where} LIMIT 1 {order}"
				, Dict.create().set("columns", queryColumns).set("table", tableName).set("logic", logic).set("where", StrUtil.isBlank(where) ? "" : where).set("order", Const.ORDER_BY.equals(order)?"":order));
		log.debug("\n【执行SQL】SQL：{}", sql);
		log.debug("【执行SQL】参数：{}", JSONUtil.toJsonStr(values));
		Long end = System.currentTimeMillis();
		log.debug("【SQL拼接用时】：{} 毫秒\n", (end-start));
		SQLUtil util=new SQLUtil();
		util.setSql(sql);
		util.setValues(values);
		return util;
	}

	private SQLUtil buildQueryListByConditions(QueryWrapper wrapper) {
		Long start = System.currentTimeMillis();
		String tableName = getTableName();
		Field logicField=getLogicField();
		String logic=buildLogic(logicField);
		List<Field> columnsField = getIgnoreField(true);
		String queryColumns=wrapper.getSelect().toString();
		if(StrUtil.isBlank(queryColumns)) {
			List<String> columnsList = getColumns(columnsField);
			queryColumns = StrUtil.join(Const.SEPARATOR_COMMA, columnsList);
		}
		String subquery= wrapper.getSubquery().toString();
		if(StrUtil.isNotBlank(queryColumns)&&StrUtil.isNotBlank(subquery)) {
			subquery=Const.SEPARATOR_COMMA+subquery;
		}
		List<Object> values = wrapper.getParameter();
		String sql = StrUtil.format("SELECT {columns} {subquery} FROM {table} {as} WHERE {logic} AND {wapper}",
				Dict.create().set("columns", queryColumns)
							 .set("subquery", subquery)
							 .set("table", tableName)
							 .set("as", Const.CONNECTOR_AS+wrapper.getTableAs())
							 .set("logic", logic)
							 .set("wapper", wrapper.getBuilder().toString()));
		log.debug("\n【执行SQL】SQL：{}", sql);
		log.debug("【执行SQL】参数：{}", JSONUtil.toJsonStr(values));
		Long end = System.currentTimeMillis();
		log.debug("【SQL拼接用时】：{} 毫秒\n", (end-start));
		SQLUtil util=new SQLUtil();
		util.setSql(sql);
		util.setValues(values.toArray());
		return util;
	}

	private SQLUtil buildPageByConditions(T t, QueryWrapper wrapper, PageInfoBean page) {
		Long start = System.currentTimeMillis();
		String tableName = getTableName(t);
		Field logicField=getLogicField();
		String logic=buildLogic(logicField);
		List<Field> columnsField = getIgnoreField(true);
		String queryColumns=wrapper.getSelect().toString();
		if(StrUtil.isBlank(queryColumns)) {
			List<String> columnsList = getColumns(columnsField);
			queryColumns = StrUtil.join(Const.SEPARATOR_COMMA, columnsList);
		}
		String subquery= wrapper.getSubquery().toString();
		if(StrUtil.isNotBlank(queryColumns)&&StrUtil.isNotBlank(subquery)) {
			subquery=Const.SEPARATOR_COMMA+subquery;
		}
		List<Field> filterField = getField(t, true);
		String where = buildWhere(filterField);
		List<Object> values = filterField.stream().map(field -> ReflectUtil.getFieldValue(t, field)).collect(Collectors.toList());
		CollectionUtil.addAll(values,wrapper.getParameter());
		String totalSql = StrUtil.format("SELECT COUNT(1) FROM {table} WHERE {logic} {where} AND {wapper}", 
				Dict.create().set("table", tableName)
							 .set("logic", logic)
							 .set("where", StrUtil.isBlank(where) ? "" : where)
							 .set("wapper", wrapper.getBuilder().toString()));
		String sql = StrUtil.format("SELECT {columns} {subquery} FROM {table} {as} WHERE {logic} {where} AND {wapper} LIMIT {start},{size}",
				Dict.create().set("columns", queryColumns)
				.set("subquery", subquery)
				.set("table", tableName).set("logic", logic)
				.set("as", Const.CONNECTOR_AS+wrapper.getTableAs())
				.set("where", StrUtil.isBlank(where) ? "" : where)
				.set("start", page.getStartIndex())
				.set("wapper", StrUtil.isBlank(wrapper.getBuilder().toString())? "TRUE": wrapper.getBuilder().toString())
				.set("size", page.getPerPage()));
		log.debug("\n【执行SQL】SQL：{}", totalSql);
		log.debug("【执行SQL】SQL：{}", sql);
		log.debug("【执行SQL】参数：{}", JSONUtil.toJsonStr(values));
		Long end = System.currentTimeMillis();
		log.debug("【SQL拼接用时】：{} 毫秒\n", (end-start));
		SQLUtil util=new SQLUtil();
		util.setTotalSql(totalSql);
		util.setSql(sql);
		util.setValues(values.toArray());
		return util;
	}
	
	private SQLUtil buildPageByConditions(QueryWrapper wrapper, PageInfoBean page) {
		Long start = System.currentTimeMillis();
		String tableName = getTableName();
		Field logicField=getLogicField();
		String logic=buildLogic(logicField);
		List<Field> columnsField = getIgnoreField(true);
		String queryColumns=wrapper.getSelect().toString();
		if(StrUtil.isBlank(queryColumns)) {
			List<String> columnsList = getColumns(columnsField);
			queryColumns = StrUtil.join(Const.SEPARATOR_COMMA, columnsList);
		}
		String subquery= wrapper.getSubquery().toString();
		if(StrUtil.isNotBlank(queryColumns)&&StrUtil.isNotBlank(subquery)) {
			subquery=Const.SEPARATOR_COMMA+subquery;
		}
		List<Object> values = wrapper.getParameter();
		String totalSql = StrUtil.format("SELECT COUNT(1) FROM {table} WHERE {logic} AND {wapper}", 
				Dict.create().set("table", tableName)
							 .set("logic", logic)
							 .set("wapper", wrapper.getBuilder().toString()));
		String sql = StrUtil.format("SELECT {columns} {subquery} FROM {table} {as} WHERE {logic} AND {wapper} LIMIT {start},{size}",
				Dict.create().set("columns", queryColumns)
				.set("subquery", subquery)
				.set("table", tableName).set("logic", logic)
				.set("as", Const.CONNECTOR_AS+wrapper.getTableAs())
				.set("start", page.getStartIndex())
				.set("wapper",  StrUtil.isBlank(wrapper.getBuilder().toString())? "TRUE": wrapper.getBuilder().toString())
				.set("size", page.getPerPage()));
		log.debug("\n【执行SQL】SQL：{}", totalSql);
		log.debug("【执行SQL】SQL：{}", sql);
		log.debug("【执行SQL】参数：{}", JSONUtil.toJsonStr(values));
		Long end = System.currentTimeMillis();
		log.debug("【SQL拼接用时】：{} 毫秒\n", (end-start));
		SQLUtil util=new SQLUtil();
		util.setTotalSql(totalSql);
		util.setSql(sql);
		util.setValues(values.toArray());
		return util;
	}

	private SQLUtil buildPageByExample(T t,PageInfoBean page) {
		Long start = System.currentTimeMillis();
		String tableName = getTableName(t);
		Field logicField=getLogicField();
		String logic=buildLogic(logicField);
		List<Field> columnsField = getIgnoreField(true);
		List<String> columnsList = getColumns(columnsField);
		String queryColumns = StrUtil.join(Const.SEPARATOR_COMMA, columnsList);
		List<Field> filterField = getField(t, true);
		List<Field> orderFile = getOrderField();
		String order = buildOrder(orderFile);
		String where = buildWhere(filterField);
		Object[] values = filterField.stream().map(field -> ReflectUtil.getFieldValue(t, field)).toArray();
		String totalSql = StrUtil.format("SELECT COUNT(1) FROM {table} WHERE {logic} {where}", Dict.create().set("table", tableName).set("logic", logic).set("where", StrUtil.isBlank(where) ? "" : where));
		String sql = StrUtil.format("SELECT {columns} FROM {table} WHERE {logic} {where} {order} LIMIT {start},{size}",
				Dict.create().set("columns", queryColumns)
				.set("table", tableName).set("logic", logic)
				.set("where", StrUtil.isBlank(where) ? "" : where)
				.set("order", Const.ORDER_BY.equals(order)?"":order)
				.set("start", page.getStartIndex())
				.set("size", page.getPerPage()));
		log.debug("\n【执行SQL】SQL：{}", totalSql);
		log.debug("【执行SQL】SQL：{}", sql);
		log.debug("【执行SQL】参数：{}", JSONUtil.toJsonStr(values));
		Long end = System.currentTimeMillis();
		log.debug("【SQL拼接用时】：{} 毫秒\n", (end-start));
		SQLUtil util=new SQLUtil();
		util.setTotalSql(totalSql);
		util.setSql(sql);
		util.setValues(values);
		return util;
	}
	
	/*---------------------------------------------------获取表（类），列（字段）---------------------------------------------------*/
	
	/**
	 * 	获取字段列表 {@code 过滤数据库中不存在的字段，以及自增列}
	 *
	 * @param t          对象
	 * @param ignore 是否忽略空值
	 * @return 字段列表
	 */
	private List<Field> getField(T t, Boolean ignore) {
		Field[] fields = ReflectUtil.getFields(t.getClass());
		List<Field> filterField;
		Stream<Field> fieldStream = CollUtil.toList(fields).stream()
			.filter(field -> ObjectUtil.isNull(field.getAnnotation(Ignore.class)))
			.filter(field -> ObjectUtil.isNull(field.getAnnotation(Transient.class)))
			.filter(field -> ObjectUtil.isNotNull(field.getAnnotation(Primarykey.class)) && !field.getAnnotation(Primarykey.class).auto() || ObjectUtil.isNull(field.getAnnotation(Primarykey.class)))
			.filter(field -> !Const.SERIALVERSION.equals(field.getName()));
		if (ignore) {
			filterField = fieldStream.filter(field -> ObjectUtil.isNotNull(ReflectUtil.getFieldValue(t, field)))
					.collect(Collectors.toList());
		} else {
			filterField = fieldStream.collect(Collectors.toList());
		}
		return filterField;
	}
	
	/**
	 * 	获取字段列表 {@code 过滤数据库中不存在的字段}
	 *
	 * @param t          对象
	 * @param ignore 是否忽略空值
	 * @return 字段列表
	 */
	/*
	private List<Field> getFieldContionsK(T t, Boolean ignore) {
		Field[] fields = ReflectUtil.getFields(t.getClass());
		List<Field> filterField;
		Stream<Field> fieldStream = CollUtil.toList(fields).stream()
			.filter(field -> ObjectUtil.isNull(field.getAnnotation(Ignore.class)))
			.filter(field -> ObjectUtil.isNull(field.getAnnotation(Transient.class)))
			.filter(field -> ObjectUtil.isNotNull(field.getAnnotation(Primarykey.class)) && !field.getAnnotation(Primarykey.class).auto() || ObjectUtil.isNull(field.getAnnotation(Primarykey.class)))
			.filter(field -> !Const.SERIALVERSION.equals(field.getName()));
		if (ignore) {
			filterField = fieldStream.filter(field -> ObjectUtil.isNotNull(ReflectUtil.getFieldValue(t, field)))
					.collect(Collectors.toList());
		} else {
			filterField = fieldStream.collect(Collectors.toList());
		}
		return filterField;
	}
	*/
	
	/**
	 * 	获取字段列表 {@code 过滤数据库中不存在的字段，以及自增列}
	 *
	 * @param t          对象
	 * @param ignore 是否忽略空值
	 * @param queryTable 是否特殊查询字段
	 * @return 字段列表
	 */
	/*
	private List<Field> getField(T t, Boolean ignore, Boolean queryTable) {
		Field[] fields = ReflectUtil.getFields(t.getClass());
		List<Field> filterField;
		Stream<Field> fieldStream = CollUtil.toList(fields).stream()
			.filter(field -> ObjectUtil.isNull(field.getAnnotation(Ignore.class)))
			.filter(field -> ObjectUtil.isNotNull(field.getAnnotation(Primarykey.class)) && !field.getAnnotation(Primarykey.class).auto() || ObjectUtil.isNull(field.getAnnotation(Primarykey.class)))
			.filter(field -> !Const.SERIALVERSION.equals(field.getName()));
		if (ignore) {
			filterField = fieldStream.filter(field -> ObjectUtil.isNotNull(ReflectUtil.getFieldValue(t, field))).collect(Collectors.toList());
		}else {
			filterField = fieldStream.collect(Collectors.toList());
		}
		if (queryTable) {
			filterField = filterField.stream().filter(field -> ObjectUtil.isNull(field.getAnnotation(QueryTable.class))).collect(Collectors.toList());
		}
		return filterField;
	}
	*/
	
	/**
	 * 	获取主键字段列表 （若联合主键）
	 *
	 * @param t    对象
	 * @return 字段列表
	 */
	/*
	private List<Field> getKeyField(T t) {
		Field[] fields = ReflectUtil.getFields(t.getClass());
		Stream<Field> primarykeyStream = CollUtil.toList(fields).stream().filter(field -> ObjectUtil.isNotNull(field.getAnnotation(Primarykey.class)));
		List<Field> primarykeyField = primarykeyStream.collect(Collectors.toList());
		return primarykeyField;
	}
	*/
	
	/**
	 * 	获取主键字段列表 （若联合主键）
	 *
	 * @return 字段列表
	 */
	private List<Field> getKeyField() {
		Field[] fields = ReflectUtil.getFields(cls);
		Stream<Field> primarykeyStream = CollUtil.toList(fields).stream().filter(field -> ObjectUtil.isNotNull(field.getAnnotation(Primarykey.class)));
		List<Field> primarykeyField = primarykeyStream.collect(Collectors.toList());
		return primarykeyField;
	}
	
	/**
	 * 	获取字段列表 {@code 过滤忽略的字段}
	 *
	 * @param t          对象
	 * @param ignore 是否忽略空值
	 * @return 字段列表
	 */
	/*
	private List<Field> getIgnoreField(T t,Boolean ignore) {
		Field[] fields = ReflectUtil.getFields(t.getClass());
		List<Field> filterField = CollUtil.toList(fields).stream()
			.filter(field -> ObjectUtil.isNull(field.getAnnotation(Ignore.class)))
			.filter(field -> !Const.SERIALVERSION.equals(field.getName()))
			.collect(Collectors.toList());
		return filterField;
	}
	*/
	
	/**
	 * 	获取字段列表 {@code 过滤忽略的字段}
	 *
	 * @param t          对象
	 * @param ignore 是否忽略空值
	 * @return 字段列表
	 */
	private List<Field> getIgnoreField(Boolean ignore) {
		Field[] fields = ReflectUtil.getFields(cls);
		List<Field> filterField = CollUtil.toList(fields).stream()
			.filter(field -> ObjectUtil.isNull(field.getAnnotation(Ignore.class)))
			.filter(field -> ObjectUtil.isNull(field.getAnnotation(Transient.class)))
			.filter(field -> !Const.SERIALVERSION.equals(field.getName()))
			.collect(Collectors.toList());
		return filterField;
	}
	
	/**
	 * 	获取需要特殊模式查询字段列表 {@link Query}
	 *
	 * @param t			对象
	 * @param ignore 是否忽略空值
	 * @return 字段列表
	 */
	/*
	private List<Field> getQuertField() {
		Field[] fields = ReflectUtil.getFields(cls);
		List<Field> filterField = CollUtil.toList(fields).stream()
			.filter(field -> ObjectUtil.isNotNull(field.getAnnotation(QueryTable.class)))
			.collect(Collectors.toList());
		return filterField;
	}
	*/
	
	/**
	 * 	获取逻辑状态字段 
	 *
	 * @param t    对象
	 * @return 字段列表
	 */
	/*
	private Field getLogicField(T t) {
		Field[] fields = ReflectUtil.getFields(t.getClass());
		Field logicField = CollUtil.toList(fields).stream().filter(field -> ObjectUtil.isNotNull(field.getAnnotation(Logic.class))).collect(Collectors.toList()).get(0);
		return logicField;
	}
	
	*/
	
	/**
	 * 	获取逻辑状态字段 
	 *
	 * @return 字段列表
	 */
	private Field getLogicField() {
		Field[] fields = ReflectUtil.getFields(cls);
		List<Field> logicFields = CollUtil.toList(fields).stream().filter(field -> ObjectUtil.isNotNull(field.getAnnotation(Logic.class))).collect(Collectors.toList());
		Field logicField = logicFields.isEmpty() ? null:logicFields.get(0) ;
		return logicField;
	}
	
	/**
	 * 	获取排序字段字
	 *
	 * @return 字段列表
	 */
	private List<Field> getOrderField() {
		Field[] fields = ReflectUtil.getFields(cls);
		List<Field> logicFields = CollUtil.toList(fields).stream().filter(field -> ObjectUtil.isNotNull(field.getAnnotation(Order.class))).collect(Collectors.toList());
		return logicFields;
	}
	
	/**
	 * 	获取表名
	 *
	 * @param t 对象
	 * @return 表名
	 */
	private String getTableName(T t) {
		Table tableAnnotation = t.getClass().getAnnotation(Table.class);
		if (ObjectUtil.isNotNull(tableAnnotation)) {
			return StrUtil.format("`{}`", tableAnnotation.name());
		} else {
			return StrUtil.format("`{}`", t.getClass().getName().toLowerCase());
		}
	}
	
	/**
	 * 	获取表名
	 *
	 * @param cls 类型
	 * @return 表名
	 */
	/*
	private String getTableName(Class<?> cls) {
		Table tableAnnotation = cls.getAnnotation(Table.class);
		if (ObjectUtil.isNotNull(tableAnnotation)) {
			return StrUtil.format("`{}`", tableAnnotation.name());
		} else {
			return StrUtil.format("`{}`", cls.getName().toLowerCase());
		}
	}
	*/

	/**
	 * 	获取表名
	 *
	 * @return 表名
	 */
	private String getTableName() {
		Table tableAnnotation = cls.getAnnotation(Table.class);
		if (ObjectUtil.isNotNull(tableAnnotation)) {
			return StrUtil.format("`{}`", tableAnnotation.name());
		} else {
			return StrUtil.format("`{}`", cls.getName().toLowerCase());
		}
	}
	
	/**
	 * 	根据{@link Column}获取字段的对应的列名
	 *
	 * @param fieldList 字段列表
	 * @return 列信息列表
	 */
	private List<String> getColumns(List<Field> fieldList) {
		// 构造列
		List<String> columnList = CollUtil.newArrayList();
		for (Field field : fieldList) {
			Column columnAnnotation = field.getAnnotation(Column.class);
			Primarykey keyAnnotation = field.getAnnotation(Primarykey.class);
			String columnName;
			if (ObjectUtil.isNotNull(columnAnnotation) && StrUtil.isNotBlank(columnAnnotation.name())) {
				columnName = columnAnnotation.name();
			} else if(ObjectUtil.isNotNull(keyAnnotation) && StrUtil.isNotBlank(keyAnnotation.name())){
				columnName=keyAnnotation.name();
			} else {
				columnName = field.getName();
			}
			columnList.add(StrUtil.format("`{}`", columnName));
		}
		return columnList;
	}
	
	/**
	 * 	根据{@link Primarykey}获取主键列（单主键）
	 *
	 * @param fieldList 字段列表
	 * @return 列信息列表
	 */
	private String getPrimarykeyColumn(List<Field> fieldList) {
		if(fieldList.size()>1) {
			log.error("【主键字段】：超过{1}个字段， 取第一个字段的主键列!");
		}
		String columnName;
		Field field = fieldList.get(0);
		Primarykey columnAnnotation = field.getAnnotation(Primarykey.class);
		if (ObjectUtil.isNotNull(columnAnnotation) && StrUtil.isNotBlank(columnAnnotation.name())) {
			columnName = columnAnnotation.name();
		} else {
			columnName = field.getName();
		}
		columnName=StrUtil.format("`{}`", columnName);
		
		return columnName;
	}
	
	/**
	 * 	根据{@link Primarykey} 注解获取主键列
	 *
	 * @param fieldList 字段列表（组合主键）
	 * @return 列信息列表
	 */
	private List<String> getPrimarykeyColumns(List<Field> fieldList) {
		// 构造列
		List<String> columnList = CollUtil.newArrayList();
		for (Field field : fieldList) {
			Primarykey columnAnnotation = field.getAnnotation(Primarykey.class);
			String columnName;
			if (ObjectUtil.isNotNull(columnAnnotation) && StrUtil.isNotBlank(columnAnnotation.name())) {
				columnName = columnAnnotation.name();
			} else {
				columnName = field.getName();
			}
			columnList.add(StrUtil.format("`{}`", columnName));
		}
		return columnList;
	}
	
	/**
	 * 	根据{@link Column}获取字段的列名
	 *
	 * @param fieldList 字段列表
	 * @return 列信息列表
	 */
	private String getColumn(Field field) {
		// 构造列
		Column columnAnnotation = field.getAnnotation(Column.class);
		Primarykey keyAnnotation = field.getAnnotation(Primarykey.class);
		String columnName="";
		if (ObjectUtil.isNotNull(columnAnnotation) && StrUtil.isNotBlank(columnAnnotation.name())) {
			columnName = columnAnnotation.name();
		} else if(ObjectUtil.isNotNull(keyAnnotation) && StrUtil.isNotBlank(keyAnnotation.name())){
			columnName=keyAnnotation.name();
		} else {
			columnName = field.getName();
		}
		columnName = StrUtil.format("`{}`", columnName);
		return columnName;
	}
	
	/*---------------------------------------------------获取注解值---------------------------------------------------*/
	
	/**
	 * 
	 * <p>Title: getLogicNormalValue</p>  
	 * <p>Description: 获取数据正常状态值</p>  
	 * @param field
	 * @return 
	 * @author WangSLi
	 * @date 2020年3月16日  
	 * @version 1.0
	 */
	private String getLogicNormalValue(Field field) {
		// 构造列
		Logic columnAnnotation = field.getAnnotation(Logic.class);
		String normalValue = "";
		if (ObjectUtil.isNotNull(columnAnnotation)) {
			normalValue = columnAnnotation.normal();
		} 
		return normalValue;
	}
	
	/**
	 * 
	 * <p>Title: getLogicDeleteValue</p>  
	 * <p>Description: 逻辑删除状态值</p>  
	 * @param field
	 * @return 
	 * @author WangSLi
	 * @date 2020年3月16日  
	 * @version 1.0
	 */
	private String getLogicDeleteValue(Field field) {
		// 构造列
		Logic columnAnnotation = field.getAnnotation(Logic.class);
		String normalValue = "";
		if (ObjectUtil.isNotNull(columnAnnotation)) {
			normalValue = columnAnnotation.delete();
		} 
		return normalValue;
	}
	
	/**
	 * 
	 * <p>Title: getQueryTable</p>  
	 * <p>Description: 获取注解中查询模式的值model()</p>  
	 * @param field
	 * @return 
	 * @author WangSLi
	 * @date 2020年3月18日  
	 * @version 1.0
	 */
	private String getQueryTable(Field field) {
		String queryModel = QueryModel.EQUALS;
		QueryTable columnAnnotation = field.getAnnotation(QueryTable.class);
		if (ObjectUtil.isNotNull(columnAnnotation)) {
			queryModel=columnAnnotation.model();
		}
		return queryModel;
	}
	
	/**
	 * 
	 * <p>Title: getOrderSort</p>  
	 * <p>Description: 获取排序字段的优先级</p>  
	 * @param field
	 * @return 
	 * @author WangSLi
	 * @date 2020年4月12日  
	 * @version 1.0
	 */
	private Integer getOrderSort(Field field) {
		Integer sort = 0;
		Order columnAnnotation = field.getAnnotation(Order.class);
		if (ObjectUtil.isNotNull(columnAnnotation)) {
			sort=columnAnnotation.sort();
		}
		return sort;
	}
	
	/**
	 * <p>Title: getOrderWay</p>  
	 * <p>Description: 获取字段排序方式</p>  
	 * @param field
	 * @return 
	 * @author WangSLi
	 * @date 2020年4月12日  
	 * @version 1.0
	 */
	private String getOrderWay(Field field) {
		String order = Const.ORDER_ASC;
		Order columnAnnotation = field.getAnnotation(Order.class);
		if (ObjectUtil.isNotNull(columnAnnotation)) {
			order=columnAnnotation.order();
		}
		return order;
	}
	
}
